﻿#include <iostream>
#include <vector>

using namespace std;

// 基类/派生类  父类/子类

// 人->学生
//class Person
//{
//public:
//protected:
//	string _name = "欧阳";
//	int _age = 20;
//	string gender = "男";
//private:
//	int _hide = 1;
//};
//
//class Student : public Person // public 继承方式
//{
//public:
//	void Print() const
//	{
//		//cout << _name << endl;
//		//cout << _age << endl;
//		//cout << gender << endl;
//		//cout << _id << endl;
//		///*cout << Person::_hide << endl; */  // err
//	}
//protected:
//	string _id = "001";
//};
//
//
//int main()
//{
//	Person p;  // 基类对象
//	Student s; // 派生类对象
//	p = s;     // 派生类对象->基类对象
//	//s = p;     // err
//	Person* ptr1 = &s;
//	Person& ptr2 = s;
//	return 0;
//}


//int main()
//{
//	Student s;
//	s.Print();
//	return 0;
//}

//class A
//{
//public:
//protected:
//	int _num = 999;
//};
//
//class B : public A
//{
//public:
//	void Print()
//	{
//		cout << _num << endl;
//		cout << A::_num << endl;
//	}
//protected:
//	int _num = 111;
//};
//
//int main()
//{
//	B b;
//	b.Print();
//	return 0;
//}

//class A
//{
//public :
//	void fun()
//	{
//		cout << "func()" << endl;
//	}
//};
//class B : public A
//{
//public :
//	void fun(int i)
//	{
//		cout << "func(int i)" << i << endl;
//	}
//};
//int main()
//{
//	B b;
//	b.fun(10);
//	b.fun();
//	return 0;
//};

//class Person
//{
//public:
//	//Person(const char* str = "xxx")
//	//	/*:_str1(str)*/
//	//{
//	//	cout << "Person()" << endl;
//	//}
//
//	Person(const Person& s)
//		:_str1(s._str1)
//	{
//		cout << "Person(const Person& s)" << endl;
//	}
//
//	Person& operator=(const Person& s)
//	{
//		cout << "Person& operator=(const Person& s)" << endl;
//		if (this != &s)
//			_str1 = s._str1;
//		return *this;
//	}
//
//	~Person()
//	{
//		cout << "~Person()" << endl;
//	}
//protected:
//	string _str1;
//};
//
//class Student : public Person
//{
//public:
//	Student(const char* name = "xxx", const string& str = "World")
//		:Person(name)
//		,_str2(str)
//	{
//		cout << "Student()" << endl;
//	}
//protected:
//	string _str2;
//};
//
//int main()
//{
//	Student s;
//	return 0;
//}

//class Person
//{
//public:
//	Person(const char* name = "xxx")
//		: _name(name)
//	{
//		cout << "Person()" << endl;
//	}
//
//	Person(const Person& p)
//		: _name(p._name)
//	{
//		cout << "Person(const Person& p)" << endl;
//	}
//
//	Person& operator=(const Person& p)
//	{
//		cout << "Person operator=(const Person& p)" << endl;
//		if (this != &p)
//			_name = p._name;
//		return *this;
//	}
//
//	~Person()
//	{
//		cout << "~Person()" << endl;
//	}
//protected:
//	string _name; // 姓名
//};
//
//class Student : public Person
//{
//public:
//	Student(const char* name, int num, const char* addrss)
//		:Person(name)
//		, _num(num)
//		, _addrss(addrss)
//	{}
//
//	// 严格说Student拷贝构造默认生成的就够用了
//	// 如果有需要深拷贝的资源，才需要自己实现
//	Student(const Student& s)
//		:Person(s)
//		, _num(s._num)
//		, _addrss(s._addrss)
//	{
//		// 深拷贝
//	}
//
//	// 严格说Student赋值重载默认生成的就够用了
//	// 如果有需要深拷贝的资源，才需要自己实现
//	Student& operator=(const Student& s)
//	{
//		if (this != &s)
//		{
//			// 父类和子类的operator=构成隐藏关系
//			Person::operator=(s);
//
//			_num = s._num;
//			_addrss = s._addrss;
//		}
//
//		return *this;
//	}
//
//	// 严格说Student析构默认生成的就够用了
//	// 如果有需要显示释放的资源，才需要自己实现
//	// 析构函数都会被特殊处理成destructor() 
//	~Student()
//	{
//		// 子类的析构和父类析构函数也构成隐藏关系
//		// 规定：不需要显示调用，子类析构函数之后，会自动调用父类析构
//		// 这样保证析构顺序，先子后父，显示调用取决于实现的人，不能保证
//		// 先子后父
//		//Person::~Person();
//		//delete _ptr[];
//	}
//protected:
//	int _num = 1; //学号
//	string _addrss = "西安市高新区";
//
//	int* _ptr = new int[10];
//};
//
//int main()
//{
//	Student s1("张三", 1, "西安市");
//	Student s2(s1);
//
//	Student s3("李四", 2, "咸阳市");
//	s1 = s3;
//
//	/*Person* ptr = new Person;
//	delete ptr;*/
//
//	return 0;
//}

// 继承类模板
//#include <vector>
//template<class T>
//class Stack : public std::vector<T>
//{
//public:
//	void Push(const T& x)
//	{
//		vector<T>::push_back(x);
//	}
//
//	void Pop()
//	{
//		vector<T>::pop_back();
//	}
//
//	T& top()
//	{
//		return vector<T>::back();
//	}
//
//	bool empty()
//	{
//		return vector<T>::empty();
//	}
//};
//
//int main()
//{
//	Stack<int> st;
//	st.Push(1);
//	st.Push(2);
//	st.Push(3);
//	while (!st.empty())
//	{
//		cout << st.top() << " ";
//		st.Pop();
//	}
//
//	return 0;
//}

//class A final
//{
//public:
//};
//
//class B : public A
//{
//public:
//};
//
//int main()
//{
//	B b;
//	return 0;
//}

//class Student;
//class Person
//{
//public :
//	friend void Display(const Person& p, const Student& s);
//protected:
//	string _name; // 姓名
//};
//class Student : public Person
//{
//public:
//	friend void Display(const Person& p, const Student& s);
//protected :
//	int _stuNum; // 学号
//};
//void Display(const Person& p, const Student& s)
//{
//	cout << p._name << endl;
//	cout << s._stuNum << endl;
//} 
//
//int main()
//{
//	Person p;
//	Student s;
//	// 编译报错：error C2248: “Student::_stuNum”: ⽆法访问 protected 成员
//	// 解决⽅案：Display也变成Student 的友元即可
//	Display(p, s);
//	return 0;
//}

//class Person
//{
//public :
//	string _name;
//	static int _count;
//};
//
//int Person::_count = 0;
//
//class Student : public Person
//{
//protected :
//	int _stuNum;
//};
//
//int main()
//{
//	Person p;
//	Student s;
//	// 这⾥的运⾏结果可以看到⾮静态成员_name的地址是不⼀样的
//	// 说明派⽣类继承下来了，⽗派⽣类对象各有⼀份
//	cout << &p._name << endl;
//	cout << &s._name << endl;
//	// 这⾥的运⾏结果可以看到静态成员_count的地址是⼀样的
//	// 说明派⽣类和基类共⽤同⼀份静态成员
//	cout << &p._count << endl;
//	cout << &s._count << endl;
//	// 公有的情况下，⽗派⽣类指定类域都可以访问静态成员
//	cout << Person::_count << endl;
//	cout << Student::_count << endl;
//	return 0;
//}


//class Person
//{
//public:
//	string _name;
//	string _gender;
//	int _age;
//};
//
//class Student : virtual public Person
//{
//protected:
//	int _StuNum;
//};
//
//class Teacher : virtual public Person
//{
//protected:
//	int _id;
//};
//
//class Total : public Student, public Teacher
//{
//protected:
//	string _data;
//};
//
//int main()
//{
//	Total tl;
//	//tl._name = "欧阳";
//	tl.Student::_name = "欧阳";
//	tl.Teacher::_name = "ouyang";
//	return 0;
//}

//class Base1 { public: int _b1; };
//class Base2 { public: int _b2; };
//class Derive : public Base1, public Base2 { public: int _d; };
//int main()
//{
//	Derive d;
//	Base1* p1 = &d;
//	Base2* p2 = &d;
//	Derive* p3 = &d;
//	cout << p1 << endl;
//	cout << p2 << endl;
//	cout << p3 << endl;
//	return 0;
//}

// 继承 is-a
class Stack1 : public std::vector<int>
{
};

// 组合 has-a
class Stack2
{
protected:
	std::vector<int> _v;
};

int main()
{
	return 0;
}